# 二、魔术函数
# __init__(): 对象的初始化函数
# __init__()，在创建一个对象时默认被调用，不需要手动调用
# __init__(self)中的self参数，不需要开发者传递，python解释器会自动把当前的对象引用传递过去。

# __new__：创建一个对象的时候会首先自动调用这个函数
# __str__: 当使用print输出对象的时候，默认打印对象的内存地址。如果类定义了 __str__方法，那么就会打印从在这个函数中 return 的数据。
# __del__：当删除对象时，python解释器也会默认调用 __del__()函数。

# 实例化一个类的对象步骤：
# 第一、调用 __new__ 方法
# 第二、调用 __init__ 方法
# 第三、一些别的显示调用的方法
# 最后、调用 __del__ 方法销毁对象

class Car():
    def __init__(self, brand, type_name, category):  # 实例化第二步：执行 __init__ 方法
        # brand,type_name,category都是对象属性(成员属性)
        print('开始初始化car对象')
        self.brand = brand
        self.type_name = type_name
        self.category = category

    def run(self):  # # run函数就是车的行为, 对象函数（成员函数）
        print(f'{self.brand} - {self.type_name} - {self.category} 开起来')

    def __new__(cls, *args, **kwargs):  # 实例化第一步：执行 __new__方法
        print('创建对象')
        # super().__new__(cls) 调用父类的 __new__函数 创建对象
        return super().__new__(cls)

    def __str__(self):
        # str魔法函数， 以后只要有print(对象), 则会自动调用str函数，并且打印str函数的返回值
        return f'汽车的品牌是:{self.brand}, 型号是:{self.type_name}， 汽车的类别是:{self.category}'

    def __del__(self):  # 对象使用完之后，最后调用 __del__ 删除对象
        # 未来 当这个对象被销毁的时候 需要做 记录日志代码，通知代码，发消息代码，这些场景
        print('开始删除对象')


car1 = Car('小米', 'ultral', '轿车')

car1.run()
print(car1)  # 当对象car1的类中，没有显示的写 __str__ 魔法函数，print(car1)打印输出的是 对象的16进制内存地址
